package com.xxxx.manager.service.impl;

import com.alibaba.druid.util.StringUtils;
import com.xxxx.common.utils.JsonUtil;
import com.xxxx.manager.mapper.GoodsCategoryMapper;
import com.xxxx.manager.pojo.GoodsCategory;
import com.xxxx.manager.pojo.GoodsCategoryExample;
import com.xxxx.manager.service.GoodsCategoryService;
import com.xxxx.manager.vo.GoodsCategoryVo;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.core.ValueOperations;
import org.springframework.stereotype.Service;

import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * @Author Str
 * @Date 2021/9/11 16:21
 * @Description :商品分类服务实现类
 */
@Service
public class GoodsCategoryServiceImpl implements GoodsCategoryService {

    @Autowired
    private GoodsCategoryMapper goodsCategoryMapper;

    @Autowired
    private RedisTemplate<String, String> redisTemplate;

    @Value("${goods.category.list.key}")
    private String goodsCategoryListKey;

    /**
     * 商品分类-新增分类-查询所有顶级分类
     *
     * @param
     * @return java.utils.List<com.xxxx.manager.pojo.GoodsCategory>
     */
    @Override
    public List<GoodsCategory> selectCategoryTopList() {
        // 创建查询对象
        GoodsCategoryExample example = new GoodsCategoryExample();
        // 设置查询条件，parent_id=0
        example.createCriteria().andParentIdEqualTo((short) 0);
        return goodsCategoryMapper.selectByExample(example);
    }

    /**
     * 商品分类-新增分类-根据父id查询子分类
     *
     * @return java.utils.List<com.xxxx.manager.pojo.GoodsCategory>
     */
    @Override
    public List<GoodsCategory> selectCategoryListByParentId(Short parentId) {
        // 创建查询对象
        GoodsCategoryExample example = new GoodsCategoryExample();
        // 设置查询条件
        example.createCriteria().andParentIdEqualTo(parentId);
        return goodsCategoryMapper.selectByExample(example);
    }

    /**
     * 商品分类-新增分类-查询商品分类（通用）
     */
    @Override
    public List<GoodsCategory> selectCategoryList(Short parentId) {
        return null;
    }

    /**
     * 商品分类-新增分类-保存分类
     *
     * @return int 受影响行数
     */
    @Override
    public int categorySave(GoodsCategory goodsCategory) {
        // 删除redis缓存中的数据，goods*是要删除的数据以goods开头
        redisTemplate.delete(redisTemplate.keys("goods*"));
        // insertSelective：选择性插入
        return goodsCategoryMapper.insertSelective(goodsCategory);
    }

    /**
     * 商品分类-列表
     * 三重for循环查询所有商品分类
     *
     * @return java.utils.List<com.xxxx.manager.vo.GoodsCategoryVo>
     */
    @Override
    public List<GoodsCategoryVo> selectCategoryListForView() {
        // 第一种写法：比较难看懂
        // 创建查询对象
//        GoodsCategoryExample example = new GoodsCategoryExample();
//        // 设置查询条件 where parent_id = 0 and level = 1
//        example.createCriteria().andParentIdEqualTo((short) 0).andLevelEqualTo((byte) 1);
//        // 查询顶级分类
//        List<GoodsCategory> gcList = goodsCategoryMapper.selectByExample(example);
//        List<GoodsCategoryVo> gcvList=new ArrayList<>();
//        for (GoodsCategory gc01 : gcList) {
//            GoodsCategoryVo gcv01 = new GoodsCategoryVo();
//            // 将GoodsCategory转换成GoodsCategoryVo
//            BeanUtils.copyProperties(gc01,gcv01);  // 拷贝属性
//            // 清空查询对象
//            example.clear();
//            // 设置查询条件
//            example.createCriteria().andParentIdEqualTo(gc01.getId()).andLevelEqualTo((byte) 2);
//            // 查询二级分类
//            List<GoodsCategory> gcList02 = goodsCategoryMapper.selectByExample(example);
//            List<GoodsCategoryVo> gcvList02 = new ArrayList<>();
//            for (GoodsCategory gc02 : gcList02) {
//                GoodsCategoryVo gcv02 = new GoodsCategoryVo();
//                BeanUtils.copyProperties(gc02,gcv02);
//                // 清空查询对象
//                example.clear();
//                // 设置查询条件
//                example.createCriteria().andParentIdEqualTo(gc02.getId()).andLevelEqualTo((byte) 3);
//                // 查询三级分类
//                List<GoodsCategory> gcList03 = goodsCategoryMapper.selectByExample(example);
//                List<GoodsCategoryVo> gcvList03 = new ArrayList<>();
//                for (GoodsCategory gc03 : gcList03) {
//                    GoodsCategoryVo gcv03 = new GoodsCategoryVo();
//                    BeanUtils.copyProperties(gc03,gcv03);
//                    gcvList03.add(gcv03);
//                }
//                // 将三级分类list放进二级分类的对象里
//                gcv02.setChildren(gcvList03);
//                gcvList02.add(gcv02);
//            }
//            // 将二级分类list放进一级分类的对象里
//            gcv01.setChildren(gcvList02);
//            gcvList.add(gcv01);
//        }
//        return gcvList;

        // 从数据库查出的数据放进redis中
        ValueOperations<String, String> valueOperations = redisTemplate.opsForValue();
        // 查询Redis缓存是否有数据，有数据直接返回，没有数据从数据库查询
        String gcvListJson = valueOperations.get(goodsCategoryListKey);
        if (!StringUtils.isEmpty(gcvListJson)) {
            return JsonUtil.jsonToList(gcvListJson, GoodsCategoryVo.class);
        }

        // =============================================================================
        // 第二种写法：jdk8新特性写法
        // 创建查询对象
        GoodsCategoryExample example = new GoodsCategoryExample();
        // 不需要条件，直接查询所有
        List<GoodsCategory> list = goodsCategoryMapper.selectByExample(example);
        // 将GoodsCategory对象转成GoodsCategoryVo对象
        List<GoodsCategoryVo> gcvList = list.stream().map(e -> {
            GoodsCategoryVo gcv = new GoodsCategoryVo();
            BeanUtils.copyProperties(e, gcv);
            return gcv;
        }).collect(Collectors.toList());
        // 将List<GoodsCategoryVo>转成Map<parentId,List<GoodsCategoryVo>>
        // 按parentId分组，key就是parentId，值就是parentId对应的List<GoodsCategoryVo>
        Map<Short, List<GoodsCategoryVo>> map = gcvList.stream().collect(Collectors.groupingBy(GoodsCategoryVo::getParentId));
        // 循环给children赋值
        gcvList.forEach(e -> e.setChildren(map.get(e.getId())));
        // 拦截器，返回level为1的list，也就是顶级分类
        List<GoodsCategoryVo> gcvList01 = gcvList.stream().filter(e -> 1 == e.getLevel()).collect(Collectors.toList());

        // 放入Redis缓存，第一次查询的时候
        valueOperations.set(goodsCategoryListKey, JsonUtil.object2JsonStr(gcvList01));
        return gcvList01;

    }

    /**
     * 商品分类-查询所有商品分类
     */
    @Override
    public List<GoodsCategory> selectCategoryList() {
        return goodsCategoryMapper.selectByExample(new GoodsCategoryExample());
    }
}
